/*
 * RT-Thread Secure
 *
 * Copyright (c) 2021, Shanghai Real-Thread Electronic Technology Co., Ltd.
 *
 * All rights reserved.
 */
#include "drv_debug.h"
#include "rtdef.h"
#include "rk3568.h"
#include "serial_reg.h"
#include "rthw.h"
#include "ioremap.h"
#include "mmu.h"

static rt_uint32_t *uart_base = 0;
void rt_hw_debug_putc(char c)
{
    rt_uint8_t status = 0;

    /* Wait for Tx FIFO not full */
    do {
        status = HWREG32(uart_base + UART_LSR);
    } while ((status & (UART_LSR_TEMT | UART_LSR_THRE)) == 0);

    HWREG32(uart_base + UART_TX) = c;
}

void rt_hw_debug_puts(const char *str)
{
    while(*str)
    {
        if(*str == '\n')
        {
            rt_hw_debug_putc('\r');
        }
        rt_hw_debug_putc(*str);
        str++;
    }
}

void rt_hw_debug_printf(const char* fmt, ...)
{
    va_list args;
    rt_size_t length;
    static char rt_log_buf[RT_CONSOLEBUF_SIZE];

    if (!uart_base)
    {
        uart_base = (rt_uint32_t *) rt_ioremap((void *) UART2_MMIO_BASE, 0x10000);
    }

    va_start(args, fmt);
    /* the return value of vsnprintf is the number of bytes that would be
     * written to buffer had if the size of the buffer been sufficiently
     * large excluding the terminating null byte. If the output string
     * would be larger than the rt_log_buf, we have to adjust the output
     * length. */
    length = rt_vsnprintf(rt_log_buf, sizeof(rt_log_buf) - 1, fmt, args);
    if (length > RT_CONSOLEBUF_SIZE - 1)
        length = RT_CONSOLEBUF_SIZE - 1;
    rt_hw_debug_puts(rt_log_buf);
    va_end(args);
}
